import { Vector2, Spherical } from "../three.module.js";

//立方体
export default class BoldLine {
    constructor(points = [], lineWidth = 1) {
        this.points = points;
        this.lineWidth = lineWidth;

        this.normals = [];//顶点法向
        this.vertices = [];//顶点信息
        this.elements = [];//默认的Elements
        this.uv = [];

        this._init();
    }

    _init() {
        const { points, lineWidth } = this;
        if (points.length < 2) return;
        const h = lineWidth / 2;

        //挤压线条, 获取顶点
        const extrudePoints = this._extrude();


        for (let i = 1; i < points.length; i++) {
            const A1 = extrudePoints[(i - 1) * 2];
            const B1 = extrudePoints[i * 2];
            const A2 = extrudePoints[(i - 1) * 2 + 1];
            const B2 = extrudePoints[i * 2 + 1];
            this.vertices.push(
                ...A1, ...A2, ...B2, ...B1,
            );

            if (i != 0) {
                const index = i * 4;
                this.elements.push(
                    index - 4, index - 3, index - 2, index - 4, index - 2, index - 1,
                );
            }

            //让角归零
            const ang = -B1.clone().sub(A1).angle();

            const O = new Vector2();
            const [lb, rt, rb] = [
                A2.clone().sub(A1).rotateAround(O, ang),
                B1.clone().sub(A1).rotateAround(O, ang),
                B2.clone().sub(A1).rotateAround(O, ang),
            ];
            this.uv.push(
                0, 1,
                lb.x / h, 0,
                rb.x / h, 0,
                rt.x / h, 1,
            );
        }
    }

    _extrude() {
        const { points, lineWidth } = this;
        //线宽的一半
        const h = lineWidth / 2;
        //挤压出来的顶点集合
        const extrudePoints = [
            ...this._verticalPoint(points[0], points[1], h)
        ];

        const len1 = points.length - 1;
        const len2 = len1 - 1;

        for (let i = 0; i < len2; i++) {
            const [A, B, C] = [
                points[i], points[i + 1], points[i + 2]
            ];
            if (this._intersect(A, B, C)) {
                //相交
                extrudePoints.push(...this._interPoint(A, B, C, h));
            } else {
                //不相交
                extrudePoints.push(...this._verticalPoint(B, C, h));
            }
        }
        extrudePoints.push(...this._verticalPoint(points[len2], points[len1], h, points[len1]));
        return extrudePoints;
    }

    //垂直挤压
    _verticalPoint(A, B, h, M = A) {
        const { x, y } = B.clone().sub(A);
        const t = new Vector2(-y, x).setLength(h).add(M);
        const b = new Vector2(y, -x).setLength(h).add(M);
        return [t, b];
    }

    //拐点挤压
    _interPoint(A, B, C, h) {
        const d = B.clone().sub(A).normalize();
        const e = B.clone().sub(C).normalize();
        const b = d.clone().add(e).normalize();
        const BG = new Vector2(d.y, -d.x).setLength(h);
        const BGLen = BG.length();//这个不是就是h
        const cos = BG.clone().dot(b) / BGLen;
        const BB2 = b.setLength(BGLen / cos);
        const BB1 = BB2.clone().negate();//取反
        return [BB1.add(B), BB2.add(B)];
    }

    //是否相交
    _intersect(A, B, C) {
        const [angAB, angBC] = [
            B.clone().sub(A).angle(),
            C.clone().sub(B).angle(),
        ];
        return (angAB - angBC) % Math.PI == 0 ? false : true;
    }
}